#!/usr/bin/env python3
# -*- coding: utf-8 -*-

"""
配置管理模块

本模块负责管理GomerX机器人的所有配置参数，包括摄像头、视觉处理、底盘、
机械臂、夹爪和任务相关的配置。提供了配置的加载、保存、更新和显示功能，
以及交互式配置菜单界面。
"""

import os
import json
from typing import Dict, Any, Tuple, List


class ConfigManager:
    """
    配置管理器类
    
    负责加载、保存和管理机器人的所有配置参数。配置数据以JSON格式存储在
    user_config.json文件中。如果配置文件不存在，将使用默认配置。
    """
    
    def __init__(self):
        """初始化配置管理器"""
        # 设置配置文件路径
        self.config_file = "user_config.json"
        # 加载配置数据
        self.config = self._load_config()
    
    def _load_config(self) -> Dict[str, Any]:
        """
        加载配置数据
        
        从配置文件中读取配置数据，如果文件不存在或格式错误，则使用默认配置。
        
        Returns:
            Dict[str, Any]: 配置数据字典
        """
        # 检查配置文件是否存在
        if os.path.exists(self.config_file):
            try:
                # 尝试打开并读取配置文件
                with open(self.config_file, 'r', encoding='utf-8') as f:
                    # 解析JSON数据并返回
                    return json.load(f)
            except (json.JSONDecodeError, IOError):
                # 如果文件格式错误或读取失败，使用默认配置
                print(f"配置文件 {self.config_file} 格式错误，使用默认配置")
                return self._get_default_config()
        else:
            # 配置文件不存在，使用默认配置
            print(f"配置文件 {self.config_file} 不存在，使用默认配置")
            return self._get_default_config()
    
    def _get_default_config(self) -> Dict[str, Any]:
        """
        获取默认配置
        
        返回包含所有模块默认参数的配置字典。
        
        Returns:
            Dict[str, Any]: 默认配置数据字典
        """
        return {
            "camera": {
                "resolution": [640, 480],  # 摄像头分辨率：宽度640像素，高度480像素
                "fps": 30,  # 摄像头帧率：每秒30帧
                "exposure": -6  # 摄像头曝光值：-6（较低曝光值适用于室内环境）
            },
            "vision": {
                "line_detection": {
                    "threshold": 127,  # 二值化阈值：127（中等阈值）
                    "min_line_length": 50,  # 最小线段长度：50像素
                    "max_line_gap": 20  # 最大线段间隙：20像素
                },
                "color_detection": {
                    "red": {  # 红色HSV范围
                        "lower": [0, 100, 100],  # HSV下限：色相0，饱和度100，明度100
                        "upper": [10, 255, 255]  # HSV上限：色相10，饱和度255，明度255
                    },
                    "blue": {  # 蓝色HSV范围
                        "lower": [100, 100, 100],  # HSV下限：色相100，饱和度100，明度100
                        "upper": [130, 255, 255]  # HSV上限：色相130，饱和度255，明度255
                    },
                    "green": {  # 绿色HSV范围
                        "lower": [40, 100, 100],  # HSV下限：色相40，饱和度100，明度100
                        "upper": [80, 255, 255]  # HSV上限：色相80，饱和度255，明度255
                    }
                },
                "object_detection": {
                    "min_contour_area": 500,  # 最小轮廓面积：500平方像素
                    "max_contour_area": 50000  # 最大轮廓面积：50000平方像素
                }
            },
            "chassis": {
                "speed": 0.2,  # 默认速度：0.2米/秒
                "turn_speed": 0.5,  # 默认转弯速度：0.5弧度/秒
                "line_follow": {
                    "kp": 0.5,  # PID比例系数：0.5
                    "ki": 0.01,  # PID积分系数：0.01
                    "kd": 0.1,  # PID微分系数：0.1
                    "target_offset": 0.0  # 目标偏移量：0.0（中心位置）
                }
            },
            "arm": {
                "default_height": 100,  # 默认高度：100毫米
                "pick_height": 50,  # 抓取高度：50毫米
                "place_height": 80,  # 放置高度：80毫米
                "speed": 50  # 移动速度：50（相对速度值）
            },
            "gripper": {
                "open_angle": 90,  # 打开角度：90度
                "close_angle": 20,  # 关闭角度：20度
                "force": 50  # 夹持力：50（相对力度值）
            },
            "led": {
                "max_brightness": 255,       # 最大亮度值
                "default_color": [255, 255, 255],  # 默认颜色（白色）
                "fade_duration": 1.0,        # 渐变效果持续时间（秒）
                "blink_interval": 0.5,       # 闪烁间隔（秒）
                "police_interval": 0.5,      # 警灯效果间隔（秒）
                "rainbow_duration": 5.0,     # 彩虹效果持续时间（秒）
                "rainbow_step_duration": 0.5 # 彩虹效果中每个颜色的持续时间（秒）
            },
            "task": {
                "target_color": "red",  # 目标颜色：红色
                "item_area": "A",  # 物品区域：A区
                "drop_area": "B",  # 放置区域：B区
                "max_attempts": 3,  # 最大尝试次数：3次
                "timeout": 30  # 任务超时时间：30秒
            }
        }
    
    def save_config(self):
        """
        保存配置数据
        
        将当前配置数据保存到配置文件中。
        """
        try:
            # 打开配置文件并写入JSON数据
            with open(self.config_file, 'w', encoding='utf-8') as f:
                # 使用json.dump将配置字典写入文件，indent=4使格式化输出
                json.dump(self.config, f, indent=4, ensure_ascii=False)
            print(f"配置已保存到 {self.config_file}")
        except IOError:
            # 如果写入失败，输出错误信息
            print(f"无法保存配置到 {self.config_file}")
    
    def get_camera_config(self) -> Dict[str, Any]:
        """
        获取摄像头配置
        
        Returns:
            Dict[str, Any]: 摄像头配置字典
        """
        return self.config.get("camera", {})
    
    def update_camera_config(self, resolution: Tuple[int, int] = None, fps: int = None, exposure: int = None):
        """
        更新摄像头配置
        
        Args:
            resolution: 分辨率元组 (宽度, 高度)
            fps: 帧率
            exposure: 曝光值
        """
        # 确保camera配置存在
        if "camera" not in self.config:
            self.config["camera"] = {}
        
        # 更新分辨率（如果提供）
        if resolution is not None:
            self.config["camera"]["resolution"] = list(resolution)
        
        # 更新帧率（如果提供）
        if fps is not None:
            self.config["camera"]["fps"] = fps
        
        # 更新曝光值（如果提供）
        if exposure is not None:
            self.config["camera"]["exposure"] = exposure
        
        # 保存更新后的配置
        self.save_config()
    
    def get_vision_config(self) -> Dict[str, Any]:
        """
        获取视觉处理配置
        
        Returns:
            Dict[str, Any]: 视觉处理配置字典
        """
        return self.config.get("vision", {})
    
    def update_vision_config(self, section: str, **kwargs):
        """
        更新视觉处理配置
        
        Args:
            section: 配置节名称，如 "line_detection", "color_detection.red" 等
            **kwargs: 要更新的配置参数
        """
        # 确保vision配置存在
        if "vision" not in self.config:
            self.config["vision"] = {}
        
        # 分割节名称，支持嵌套访问（如 "color_detection.red"）
        section_parts = section.split('.')
        current_section = self.config["vision"]
        
        # 遍历节名称部分，创建嵌套结构（如果不存在）
        for part in section_parts[:-1]:
            if part not in current_section:
                current_section[part] = {}
            current_section = current_section[part]
        
        # 获取最后一节名称
        last_section = section_parts[-1]
        
        # 确保最后一节存在
        if last_section not in current_section:
            current_section[last_section] = {}
        
        # 更新配置参数
        for key, value in kwargs.items():
            current_section[last_section][key] = value
        
        # 保存更新后的配置
        self.save_config()
    
    def get_chassis_config(self) -> Dict[str, Any]:
        """
        获取底盘配置
        
        Returns:
            Dict[str, Any]: 底盘配置字典
        """
        return self.config.get("chassis", {})
    
    def update_chassis_config(self, section: str = None, **kwargs):
        """
        更新底盘配置
        
        Args:
            section: 配置节名称，如 "line_follow"，如果为None则更新根级配置
            **kwargs: 要更新的配置参数
        """
        # 确保chassis配置存在
        if "chassis" not in self.config:
            self.config["chassis"] = {}
        
        # 如果指定了节名称
        if section:
            # 确保节存在
            if section not in self.config["chassis"]:
                self.config["chassis"][section] = {}
            
            # 更新节中的配置参数
            for key, value in kwargs.items():
                self.config["chassis"][section][key] = value
        else:
            # 更新根级配置参数
            for key, value in kwargs.items():
                self.config["chassis"][key] = value
        
        # 保存更新后的配置
        self.save_config()
    
    def get_arm_config(self) -> Dict[str, Any]:
        """
        获取机械臂配置
        
        Returns:
            Dict[str, Any]: 机械臂配置字典
        """
        return self.config.get("arm", {})
    
    def update_arm_config(self, **kwargs):
        """
        更新机械臂配置
        
        Args:
            **kwargs: 要更新的配置参数
        """
        # 确保arm配置存在
        if "arm" not in self.config:
            self.config["arm"] = {}
        
        # 更新配置参数
        for key, value in kwargs.items():
            self.config["arm"][key] = value
        
        # 保存更新后的配置
        self.save_config()
    
    def get_gripper_config(self) -> Dict[str, Any]:
        """
        获取夹爪配置
        
        Returns:
            Dict[str, Any]: 夹爪配置字典
        """
        return self.config.get("gripper", {})
    
    def update_gripper_config(self, **kwargs):
        """
        更新夹爪配置
        
        Args:
            **kwargs: 要更新的配置参数
        """
        # 确保gripper配置存在
        if "gripper" not in self.config:
            self.config["gripper"] = {}
        
        # 更新配置参数
        for key, value in kwargs.items():
            self.config["gripper"][key] = value
        
        # 保存更新后的配置
        self.save_config()
    
    def get_led_config(self) -> Dict[str, Any]:
        """
        获取LED配置
        
        Returns:
            Dict[str, Any]: LED配置字典
        """
        return self.config.get("led", {})
    
    def update_led_config(self, **kwargs):
        """
        更新LED配置
        
        Args:
            **kwargs: 要更新的配置参数
        """
        # 确保led配置存在
        if "led" not in self.config:
            self.config["led"] = {}
        
        # 更新配置参数
        for key, value in kwargs.items():
            self.config["led"][key] = value
        
        # 保存更新后的配置
        self.save_config()
    
    def get_task_config(self) -> Dict[str, Any]:
        """
        获取任务配置
        
        Returns:
            Dict[str, Any]: 任务配置字典
        """
        return self.config.get("task", {})
    
    def update_task_config(self, **kwargs):
        """
        更新任务配置
        
        Args:
            **kwargs: 要更新的配置参数
        """
        # 确保task配置存在
        if "task" not in self.config:
            self.config["task"] = {}
        
        # 更新配置参数
        for key, value in kwargs.items():
            self.config["task"][key] = value
        
        # 保存更新后的配置
        self.save_config()
    
    def reset_to_default(self):
        """
        重置为默认配置
        
        将所有配置恢复为默认值。
        """
        # 获取默认配置
        self.config = self._get_default_config()
        # 保存配置
        self.save_config()
        print("配置已重置为默认值")


def config_menu():
    """
    配置菜单主界面
    
    提供交互式配置菜单，允许用户查看和修改机器人的各项配置参数。
    """
    # 创建配置管理器实例
    config_manager = ConfigManager()
    
    # 无限循环，直到用户选择退出
    while True:
        # 显示配置菜单标题
        print("\nGomerX 机器人配置菜单")
        print("=" * 50)
        # 显示配置选项
        print("1. 摄像头配置")
        print("2. 视觉处理配置")
        print("3. 底盘配置")
        print("4. 机械臂配置")
        print("5. 夹爪配置")
        print("6. 任务配置")
        print("7. 显示当前配置")
        print("8. 重置为默认配置")
        print("9. 退出")
        
        # 获取用户选择
        choice = input("\n请输入选项 (1-9): ").strip()
        
        # 根据用户选择执行相应操作
        if choice == "1":
            # 摄像头配置
            camera_config_menu(config_manager)
        elif choice == "2":
            # 视觉处理配置
            vision_config_menu(config_manager)
        elif choice == "3":
            # 底盘配置
            chassis_config_menu(config_manager)
        elif choice == "4":
            # 机械臂配置
            arm_config_menu(config_manager)
        elif choice == "5":
            # 夹爪配置
            gripper_config_menu(config_manager)
        elif choice == "6":
            # 任务配置
            task_config_menu(config_manager)
        elif choice == "7":
            # 显示当前配置
            show_current_config(config_manager)
        elif choice == "8":
            # 重置为默认配置
            if input("确认重置为默认配置? (y/n): ").strip().lower() == 'y':
                config_manager.reset_to_default()
                print("已重置为默认配置")
        elif choice == "9":
            # 退出菜单
            break
        else:
            # 无效选项
            print("无效选项，请重新输入")


def camera_config_menu(config_manager):
    """
    摄像头配置菜单
    
    Args:
        config_manager: 配置管理器实例
    """
    # 显示摄像头配置标题
    print("\n摄像头配置")
    print("-" * 30)
    
    # 获取当前摄像头配置
    config = config_manager.get_camera_config()
    # 显示当前配置值
    print(f"当前分辨率: {config['resolution']}")
    print(f"当前帧率: {config['fps']}")
    print(f"当前曝光值: {config['exposure']}")
    
    # 显示配置选项
    print("\n请选择要调整的参数:")
    print("1. 分辨率")
    print("2. 帧率")
    print("3. 曝光值")
    print("4. 返回上级菜单")
    
    # 获取用户选择
    choice = input("\n请输入选项 (1-4): ").strip()
    
    # 根据用户选择执行相应操作
    if choice == "1":
        # 更新分辨率
        try:
            # 获取用户输入的宽度和高度
            width = int(input("请输入宽度: "))
            height = int(input("请输入高度: "))
            # 更新配置
            config_manager.update_camera_config(resolution=(width, height))
            print("分辨率已更新")
        except ValueError:
            # 输入无效
            print("输入无效，请输入数字")
    elif choice == "2":
        # 更新帧率
        try:
            # 获取用户输入的帧率
            fps = int(input("请输入帧率: "))
            # 更新配置
            config_manager.update_camera_config(fps=fps)
            print("帧率已更新")
        except ValueError:
            # 输入无效
            print("输入无效，请输入数字")
    elif choice == "3":
        # 更新曝光值
        try:
            # 获取用户输入的曝光值
            exposure = int(input("请输入曝光值: "))
            # 更新配置
            config_manager.update_camera_config(exposure=exposure)
            print("曝光值已更新")
        except ValueError:
            # 输入无效
            print("输入无效，请输入数字")


def vision_config_menu(config_manager):
    """
    视觉处理配置菜单
    
    Args:
        config_manager: 配置管理器实例
    """
    # 显示视觉处理配置标题
    print("\n视觉处理配置")
    print("-" * 30)
    
    # 获取当前视觉处理配置
    config = config_manager.get_vision_config()
    
    # 显示配置类别选项
    print("\n请选择要调整的参数类别:")
    print("1. 线条检测参数")
    print("2. 颜色识别参数")
    print("3. 物品识别参数")
    print("4. 返回上级菜单")
    
    # 获取用户选择
    choice = input("\n请输入选项 (1-4): ").strip()
    
    # 根据用户选择执行相应操作
    if choice == "1":
        # 线条检测参数配置
        line_config = config["line_detection"]
        # 显示当前配置值
        print(f"当前二值化阈值: {line_config['threshold']}")
        print(f"当前最小线段长度: {line_config['min_line_length']}")
        print(f"当前最大线段间隙: {line_config['max_line_gap']}")
        
        try:
            # 获取用户输入的参数值
            threshold = int(input("请输入二值化阈值: "))
            min_length = int(input("请输入最小线段长度: "))
            max_gap = int(input("请输入最大线段间隙: "))
            
            # 更新配置
            config_manager.update_vision_config(
                section="line_detection",
                threshold=threshold,
                min_line_length=min_length,
                max_line_gap=max_gap
            )
            print("线条检测参数已更新")
        except ValueError:
            # 输入无效
            print("输入无效，请输入数字")
            
    elif choice == "2":
        # 颜色识别参数配置
        print("当前支持的颜色: red, blue, green")
        # 获取用户输入的颜色名称
        color = input("请输入要调整的颜色名称: ").strip().lower()
        
        # 检查颜色是否支持
        if color in config["color_detection"]:
            # 获取该颜色的当前配置
            color_config = config["color_detection"][color]
            # 显示当前配置值
            print(f"当前 {color} 色HSV下限: {color_config['lower']}")
            print(f"当前 {color} 色HSV上限: {color_config['upper']}")
            
            try:
                # 获取用户输入的HSV值
                h_min = int(input("请输入色相下限: "))
                s_min = int(input("请输入饱和度下限: "))
                v_min = int(input("请输入明度下限: "))
                h_max = int(input("请输入色相上限: "))
                s_max = int(input("请输入饱和度上限: "))
                v_max = int(input("请输入明度上限: "))
                
                # 更新配置
                config_manager.update_vision_config(
                    section=f"color_detection.{color}",
                    lower=[h_min, s_min, v_min],
                    upper=[h_max, s_max, v_max]
                )
                print(f"{color} 色识别参数已更新")
            except ValueError:
                # 输入无效
                print("输入无效，请输入数字")
        else:
            # 不支持的颜色
            print(f"不支持的颜色: {color}")
            
    elif choice == "3":
        # 物品识别参数配置
        object_config = config["object_detection"]
        # 显示当前配置值
        print(f"当前最小轮廓面积: {object_config['min_contour_area']}")
        print(f"当前最大轮廓面积: {object_config['max_contour_area']}")
        
        try:
            # 获取用户输入的轮廓面积
            min_area = int(input("请输入最小轮廓面积: "))
            max_area = int(input("请输入最大轮廓面积: "))
            
            # 更新配置
            config_manager.update_vision_config(
                section="object_detection",
                min_contour_area=min_area,
                max_contour_area=max_area
            )
            print("物品识别参数已更新")
        except ValueError:
            # 输入无效
            print("输入无效，请输入数字")


def chassis_config_menu(config_manager):
    """
    底盘配置菜单
    
    Args:
        config_manager: 配置管理器实例
    """
    # 显示底盘配置标题
    print("\n底盘配置")
    print("-" * 30)
    
    # 获取当前底盘配置
    config = config_manager.get_chassis_config()
    
    # 显示配置类别选项
    print("\n请选择要调整的参数类别:")
    print("1. 基本运动参数")
    print("2. 循迹PID参数")
    print("3. 返回上级菜单")
    
    # 获取用户选择
    choice = input("\n请输入选项 (1-3): ").strip()
    
    # 根据用户选择执行相应操作
    if choice == "1":
        # 基本运动参数配置
        # 显示当前配置值
        print(f"当前默认速度: {config['speed']} m/s")
        print(f"当前默认转弯速度: {config['turn_speed']} rad/s")
        
        try:
            # 获取用户输入的速度参数
            speed = float(input("请输入默认速度 (m/s): "))
            turn_speed = float(input("请输入默认转弯速度 (rad/s): "))
            
            # 更新配置
            config_manager.update_chassis_config(
                speed=speed,
                turn_speed=turn_speed
            )
            print("基本运动参数已更新")
        except ValueError:
            # 输入无效
            print("输入无效，请输入数字")
            
    elif choice == "2":
        # 循迹PID参数配置
        line_follow = config["line_follow"]
        # 显示当前配置值
        print(f"当前PID比例系数: {line_follow['kp']}")
        print(f"当前PID积分系数: {line_follow['ki']}")
        print(f"当前PID微分系数: {line_follow['kd']}")
        print(f"当前目标偏移量: {line_follow['target_offset']}")
        
        try:
            # 获取用户输入的PID参数
            kp = float(input("请输入PID比例系数: "))
            ki = float(input("请输入PID积分系数: "))
            kd = float(input("请输入PID微分系数: "))
            target_offset = float(input("请输入目标偏移量: "))
            
            # 更新配置
            config_manager.update_chassis_config(
                section="line_follow",
                kp=kp,
                ki=ki,
                kd=kd,
                target_offset=target_offset
            )
            print("循迹PID参数已更新")
        except ValueError:
            # 输入无效
            print("输入无效，请输入数字")


def arm_config_menu(config_manager):
    """
    机械臂配置菜单
    
    Args:
        config_manager: 配置管理器实例
    """
    # 显示机械臂配置标题
    print("\n机械臂配置")
    print("-" * 30)
    
    # 获取当前机械臂配置
    config = config_manager.get_arm_config()
    # 显示当前配置值
    print(f"当前默认高度: {config['default_height']} mm")
    print(f"当前抓取高度: {config['pick_height']} mm")
    print(f"当前放置高度: {config['place_height']} mm")
    print(f"当前移动速度: {config['speed']}")
    
    try:
        # 获取用户输入的机械臂参数
        default_height = int(input("请输入默认高度 (mm): "))
        pick_height = int(input("请输入抓取高度 (mm): "))
        place_height = int(input("请输入放置高度 (mm): "))
        speed = int(input("请输入移动速度: "))
        
        # 更新配置
        config_manager.update_arm_config(
            default_height=default_height,
            pick_height=pick_height,
            place_height=place_height,
            speed=speed
        )
        print("机械臂配置已更新")
    except ValueError:
        # 输入无效
        print("输入无效，请输入数字")


def gripper_config_menu(config_manager):
    """
    夹爪配置菜单
    
    Args:
        config_manager: 配置管理器实例
    """
    # 显示夹爪配置标题
    print("\n夹爪配置")
    print("-" * 30)
    
    # 获取当前夹爪配置
    config = config_manager.get_gripper_config()
    # 显示当前配置值
    print(f"当前打开角度: {config['open_angle']}°")
    print(f"当前关闭角度: {config['close_angle']}°")
    print(f"当前夹持力: {config['force']}")
    
    try:
        # 获取用户输入的夹爪参数
        open_angle = int(input("请输入打开角度: "))
        close_angle = int(input("请输入关闭角度: "))
        force = int(input("请输入夹持力: "))
        
        # 更新配置
        config_manager.update_gripper_config(
            open_angle=open_angle,
            close_angle=close_angle,
            force=force
        )
        print("夹爪配置已更新")
    except ValueError:
        # 输入无效
        print("输入无效，请输入数字")


def task_config_menu(config_manager):
    """
    任务配置菜单
    
    Args:
        config_manager: 配置管理器实例
    """
    # 显示任务配置标题
    print("\n任务配置")
    print("-" * 30)
    
    # 获取当前任务配置
    config = config_manager.get_task_config()
    # 显示当前配置值
    print(f"当前目标颜色: {config['target_color']}")
    print(f"当前物品区域: {config['item_area']}")
    print(f"当前放置区域: {config['drop_area']}")
    print(f"当前最大尝试次数: {config['max_attempts']}")
    print(f"当前任务超时时间: {config['timeout']} 秒")
    
    # 获取用户输入的任务参数
    target_color = input("请输入目标颜色 (red/blue/green): ").strip().lower()
    item_area = input("请输入物品区域标识: ").strip()
    drop_area = input("请输入放置区域标识: ").strip()
    
    try:
        # 获取用户输入的数值参数
        max_attempts = int(input("请输入最大尝试次数: "))
        timeout = int(input("请输入任务超时时间 (秒): "))
        
        # 更新配置
        config_manager.update_task_config(
            target_color=target_color,
            item_area=item_area,
            drop_area=drop_area,
            max_attempts=max_attempts,
            timeout=timeout
        )
        print("任务配置已更新")
    except ValueError:
        # 输入无效
        print("输入无效，请输入数字")


def show_current_config(config_manager):
    """
    显示当前配置
    
    Args:
        config_manager: 配置管理器实例
    """
    # 显示配置标题
    print("\n当前配置")
    print("=" * 50)
    
    # 获取并显示摄像头配置
    camera_config = config_manager.get_camera_config()
    print(f"摄像头分辨率: {camera_config['resolution']}")
    print(f"摄像头帧率: {camera_config['fps']}")
    
    # 获取并显示视觉处理配置
    vision_config = config_manager.get_vision_config()
    print(f"线条检测阈值: {vision_config['line_detection']['threshold']}")
    
    # 获取并显示底盘配置
    chassis_config = config_manager.get_chassis_config()
    print(f"底盘速度: {chassis_config['speed']} m/s")
    
    # 获取并显示机械臂配置
    arm_config = config_manager.get_arm_config()
    print(f"机械臂默认高度: {arm_config['default_height']} mm")
    
    # 获取并显示夹爪配置
    gripper_config = config_manager.get_gripper_config()
    print(f"夹爪打开角度: {gripper_config['open_angle']}°")
    
    # 获取并显示任务配置
    task_config = config_manager.get_task_config()
    print(f"目标颜色: {task_config['target_color']}")


# 主程序入口
if __name__ == "__main__":
    # 启动配置菜单
    config_menu()